<template>
  <div class="exec-modal">
    <je-panel>
      <template #top>
        <div class="exec-title exec-title-top exec-title-bottom">查询条件</div>
        <div class="exec-form">
          <je-form class="je-exec-form">
            <je-form-item label="参数" :colon="false" class="exec-param">
              <je-input
                v-model:value="formState.params"
                placeholder="例:{userCode:'@USER_CODE@',deptName:'总经理办公室'}"
              />
            </je-form-item>
            <je-form-item label="展示条数" :colon="false" class="exec-size">
              <je-select v-model:value="formState.size" :options="sizeOptions"></je-select>
            </je-form-item>
            <je-button type="primary" @click="handleExecQuery">
              <template #icon><i class="fas fa-caret-right"></i></template>
              执行
            </je-button>
          </je-form>
        </div>
        <div class="exec-title exec-result exec-title-top">
          <div>查询结果</div>
          <div class="exec-result-btns">
            <div class="exec-btn" @click="handleJson">查看JSON数据</div>
            <div class="exec-btn" @click="handleCompose">智能排版</div>
          </div>
        </div>
      </template>
      <template #default>
        <je-grid
          ref="xTable"
          border
          keep-source
          :data="execTableData"
          :auto-load="true"
          size="small"
          class="exec-grid-box"
        >
          <je-column type="seq" width="50" title="No." fixed="left" align="center" />
          <je-column
            v-for="itemField in cloumnFields"
            :key="itemField.field"
            :width="itemField.width"
            :field="itemField.field"
            :title="itemField.title"
          ></je-column>
        </je-grid>
      </template>
    </je-panel>
  </div>
  <je-modal
    v-model:visible="visibleJson"
    title="查看JSON数据"
    :resize="false"
    :button-align="'center'"
    class="custom-modal"
    cancel-text="关闭"
    @close="handleCancelEditor"
  >
    <template #default>
      <div class="check-json-box">
        <je-editor-code
          ref="editor"
          v-model:value="jsonContent"
          v-model:language="language"
          height="100%"
          width="100%"
          :readonly="readonly"
        />
      </div>
    </template>
  </je-modal>
</template>

<script>
  import { defineComponent, reactive, toRefs, onMounted, nextTick, watch } from 'vue';
  import { Panel, Form, Input, Button, Grid, Data, Modal } from '@jecloud/ui';
  import { execScript, isPromise, isNotEmpty, decode } from '@jecloud/utils';
  import { useJE } from '@common/helper/je';
  import { SOURCE_EXEC_SIZES } from '@/helper/constant';
  import { useSourceStore } from '@/store/source-store';
  import { sourceExecuteSql, getSourceTableFields } from '@/api/index';
  export default defineComponent({
    name: 'ExecModal',
    components: {
      JePanel: Panel,
      JeForm: Form,
      JeFormItem: Form.Item,
      JeInput: Input,
      JeButton: Button,
      JeGrid: Grid,
      JeColumn: Grid.Column,
    },
    props: {
      execData: {
        type: Object,
      },
    },
    setup(props) {
      const sourceStore = useSourceStore();
      const state = reactive({
        formState: {
          params: '', //参数
          size: 30, //展示条数
        },
        sizeOptions: SOURCE_EXEC_SIZES,
        gridStore: Data.Store.useGridStore({
          data: props.execData.data,
        }),
        cloumnFields: [], //字段属性
        execTableData: [], //当前数据
        visibleJson: false, //查看json弹窗
        language: 'json', //查看json编辑器语言
        jsonContent: '', //json内容
        readonly: true,
      });
      const formatExecField = (fields) => {
        state.cloumnFields = [];
        //整理执行结果数据为列表需要的格式
        fields.forEach((fieldItem) => {
          let curFileItem = {
            field: fieldItem,
            title: fieldItem,
            width: '120',
          };
          state.cloumnFields.push(curFileItem);
        });
      };
      //执行js语句返回结果
      const execScriptResult = (executeJs, params = {}) => {
        let flag = true;
        if (isNotEmpty(executeJs)) {
          flag = execScript(executeJs, {
            EventOptions: { isTrusted: true, type: 'dataSource', params: params },
            JE: useJE(),
          });
          if (isPromise(flag)) {
            return flag;
          } else {
            return flag !== false ? Promise.resolve(flag) : Promise.reject();
          }
        }
      };
      const methods = {
        //执行操作
        handleExecQuery() {
          const curSourceCode = sourceStore.getSourceCode();
          const curSourceData = sourceStore.getSourceDataByCode(curSourceCode);
          const decodeParams = decode(state.formState.params);
          switch (curSourceData.DATASOURCE_TYPE) {
            case 'VIEW': //视图
              //判断是否有输出视图
              if (curSourceData.DATASOURCE_OUTPUT_COLUMNS != '') {
                const outputColumns = JSON.parse(curSourceData.DATASOURCE_OUTPUT_COLUMNS);
                if (outputColumns.length > 0) {
                  const strParamData = {
                    masterTableId: '',
                    viewColumn: [],
                    viewOuput: [],
                    queryConfigVo: [],
                  };
                  //关系表
                  if (curSourceData.DATASOURCE_BASE_TABLE) {
                    const tableList = JSON.parse(curSourceData.DATASOURCE_BASE_TABLE);
                    strParamData.masterTableId = tableList[0]?.tableId;
                  }
                  //关联设计
                  if (curSourceData.DATASOURCE_INCIDENCE_RELATION) {
                    const viewColumn = JSON.parse(curSourceData.DATASOURCE_INCIDENCE_RELATION);
                    strParamData.viewColumn = viewColumn;
                  }
                  //输出视图
                  if (curSourceData.DATASOURCE_OUTPUT_COLUMNS) {
                    const viewOuput = JSON.parse(curSourceData.DATASOURCE_OUTPUT_COLUMNS);
                    strParamData.viewOuput = viewOuput;
                  }
                  //查询配置
                  if (decodeParams) {
                    if (curSourceData.DATASOURCE_CONFIG) {
                      const queryConfigVo = JSON.parse(curSourceData.DATASOURCE_CONFIG);
                      if (queryConfigVo.jsScript) {
                        execScriptResult(queryConfigVo.jsScript, decodeParams).then((res) => {
                          if (res) {
                            const execObj = {};
                            //存在参数
                            if (res.params) {
                              execObj.params = res.params;
                            }
                            //存在执行条件
                            if (res.querys) {
                              execObj.querys = res.querys;
                            }
                            queryConfigVo.editorFn = execObj;
                          } else {
                            queryConfigVo.editorFn = '';
                          }
                          strParamData.queryConfigVo = queryConfigVo;
                        });
                      }
                      setTimeout(() => {
                        const viewParam = {
                          config: JSON.stringify(strParamData),
                          parameterStr: decodeParams ? JSON.stringify(decodeParams) : '',
                          limit: state.formState.size,
                          JE_CORE_DATASOURCE_ID: curSourceData.JE_CORE_DATASOURCE_ID,
                        };
                        sourceExecuteSql(viewParam)
                          .then((res) => {
                            if (res.success) {
                              methods.setExexTableData(res.data.listData);
                            } else {
                              // methods.setExexTableData();
                              Modal.alert(res.message, 'error');
                            }
                          })
                          .catch((err) => {
                            console.log('err', err);
                            methods.setExexTableData();
                          });
                      }, 0);
                    }
                  } else {
                    strParamData.queryConfigVo = JSON.parse(curSourceData.DATASOURCE_CONFIG);
                    const viewParam = {
                      config: JSON.stringify(strParamData),
                      parameterStr: decodeParams ? JSON.stringify(decodeParams) : '',
                      limit: state.formState.size,
                      JE_CORE_DATASOURCE_ID: curSourceData.JE_CORE_DATASOURCE_ID,
                    };
                    sourceExecuteSql(viewParam)
                      .then((res) => {
                        if (res.success) {
                          methods.setExexTableData(res.data.listData);
                        } else {
                          // methods.setExexTableData();
                          Modal.alert(res.message, 'error');
                        }
                      })
                      .catch((err) => {
                        console.log('err', err);
                        methods.setExexTableData();
                      });
                  }
                } else {
                  Modal.alert('请先进行选择数据信息', 'warning');
                }
              } else {
                Modal.alert('请先进行选择数据信息', 'warning');
              }
              break;
            case 'SQL': //SQL
              if (curSourceData.DATASOURCE_DATA) {
                const viewParam = {
                  config: curSourceData.JE_CORE_DATASOURCE_ID,
                  parameterStr: decodeParams ? JSON.stringify(decodeParams) : '',
                  limit: state.formState.size,
                  JE_CORE_DATASOURCE_ID: curSourceData.JE_CORE_DATASOURCE_ID,
                };
                sourceExecuteSql(viewParam)
                  .then((res) => {
                    if (res.success) {
                      methods.setExexTableData(res.data.listData);
                    } else {
                      // methods.setExexTableData();
                      Modal.alert(res.message, 'error');
                    }
                  })
                  .catch((err) => {
                    console.log('err', err);
                    // methods.setExexTableData();
                    Modal.alert(err, 'error');
                  });
              } else {
                Modal.alert('请先进行SQL编写', 'warning');
              }
              break;
            case 'JS':
              let paramsObj = {};
              if (decodeParams) {
                paramsObj = decodeParams;
              }
              execScriptResult(curSourceData.DATASOURCE_CONFIG, paramsObj).then((res) => {
                if (res) {
                  res.fields && formatExecField(res.fields);
                  res.data && methods.setExexTableData(res.data);
                } else {
                  methods.setExexTableData();
                }
              });
              break;
            case 'ACTION': //接口ACTION
            case 'SERVICE': //service数据源
              if (curSourceData.DATASOURCE_CONFIG) {
                const actionParam = {
                  config: curSourceData.DATASOURCE_CONFIG,
                  parameterStr: decodeParams ? JSON.stringify(decodeParams) : '',
                  limit: state.formState.size,
                  JE_CORE_DATASOURCE_ID: curSourceData.JE_CORE_DATASOURCE_ID,
                };
                sourceExecuteSql(actionParam)
                  .then((res) => {
                    if (res.success) {
                      methods.setExexTableData(res.data.listData);
                    } else {
                      // methods.setExexTableData();
                      Modal.alert(res.message, 'error');
                    }
                  })
                  .catch((err) => {
                    console.log('err', err);
                    methods.setExexTableData();
                  });
              }
              break;
            case 'TABLE':
              //数据配置
              const strParamData = {
                queryConfigVo: [],
              };
              if (decodeParams) {
                if (curSourceData.DATASOURCE_CONFIG) {
                  const queryConfigVo = JSON.parse(curSourceData.DATASOURCE_CONFIG);
                  if (queryConfigVo.jsScript) {
                    execScriptResult(queryConfigVo.jsScript, decodeParams).then((res) => {
                      if (res) {
                        const execObj = {};
                        //存在参数
                        if (res.params) {
                          execObj.params = res.params;
                        }
                        //存在执行条件
                        if (res.querys) {
                          execObj.querys = res.querys;
                        }
                        queryConfigVo.editorFn = execObj;
                      } else {
                        queryConfigVo.editorFn = '';
                      }
                      strParamData.queryConfigVo = queryConfigVo;
                    });
                  } else {
                    strParamData.queryConfigVo = queryConfigVo;
                  }
                  setTimeout(() => {
                    const viewParam = {
                      config: JSON.stringify(strParamData),
                      parameterStr: decodeParams ? JSON.stringify(decodeParams) : '',
                      limit: state.formState.size,
                      JE_CORE_DATASOURCE_ID: curSourceData.JE_CORE_DATASOURCE_ID,
                    };
                    sourceExecuteSql(viewParam)
                      .then((res) => {
                        if (res.success) {
                          //判断是否有字段存在
                          if (state.cloumnFields.length == 0) {
                            const fieldData = res.data.listData[0];
                            const fieldArr = [];
                            for (let fieldKey in fieldData) {
                              fieldArr.push(fieldKey);
                            }
                            formatExecField(fieldArr);
                          }
                          methods.setExexTableData(res.data.listData);
                        } else {
                          // methods.setExexTableData();
                          Modal.alert(res.message, 'error');
                        }
                      })
                      .catch((err) => {
                        console.log('err', err);
                        methods.setExexTableData();
                      });
                  }, 0);
                }
              } else {
                strParamData.queryConfigVo = JSON.parse(curSourceData.DATASOURCE_CONFIG);
                const viewParam = {
                  config: JSON.stringify(strParamData),
                  parameterStr: decodeParams ? JSON.stringify(decodeParams) : '',
                  limit: state.formState.size,
                  JE_CORE_DATASOURCE_ID: curSourceData.JE_CORE_DATASOURCE_ID,
                };
                sourceExecuteSql(viewParam)
                  .then((res) => {
                    if (res.success) {
                      //判断是否有字段存在
                      if (state.cloumnFields.length == 0) {
                        const fieldData = res.data.listData[0];
                        const fieldArr = [];
                        for (let fieldKey in fieldData) {
                          fieldArr.push(fieldKey);
                        }
                        formatExecField(fieldArr);
                      }
                      methods.setExexTableData(res.data.listData);
                    } else {
                      // methods.setExexTableData();
                      Modal.alert(res.message, 'error');
                    }
                  })
                  .catch((err) => {
                    console.log('err', err);
                    methods.setExexTableData();
                  });
              }
              break;
            default:
              break;
          }
        },
        //设置执行列表数据
        setExexTableData(data = []) {
          //根据页面显示条数进行渲染
          const curData = data.splice(0, state.formState.size);
          state.execTableData = curData;
          state.jsonContent = JSON.stringify(curData, null, 2);
        },
        //智能排版
        handleCompose() {
          const columnArray = [];
          state.cloumnFields.forEach((item) => {
            const field = item.field;
            let num = 0,
              basics = 12,
              width = 0;

            state.execTableData.forEach((record) => {
              if (num < String(record[field]).length) {
                num = String(record[field]).length;
              }
            });
            width = num * basics;
            if (width > 100) {
              item.width = width;
            }
            if (width > 500) {
              item.width = 500;
            }
            //标题的长度
            const titleWidth = item.title.length * 25;
            if (width < titleWidth && titleWidth > 100) {
              item.width = titleWidth;
            }
            columnArray.push(item);
          });
          setTimeout(() => {
            state.cloumnFields = [...columnArray];
            state.execTableData = [...state.execTableData];
          }, 0);
        },
        //查看json数据
        handleJson() {
          state.visibleJson = true;
        },
      };
      watch(
        () => props.execData,
        (newVal) => {
          state.execTableData = newVal.data;
          state.cloumnFields = newVal.fields;
        },
        { deep: true },
      );
      onMounted(() => {
        //格式化字段
        nextTick(() => {
          methods.setExexTableData(props.execData.data);
        });
        const curSourceCode = sourceStore.getSourceCode();
        const curSourceData = sourceStore.getSourceDataByCode(curSourceCode);
        if (curSourceData.DATASOURCE_TYPE == 'TABLE') {
          const tableConfig = JSON.parse(curSourceData.DATASOURCE_CONFIG);
          //获取资源表字段
          getSourceTableFields({
            tableCode: tableConfig.tableCode,
            JE_CORE_DATASOURCE_ID: curSourceData.JE_CORE_DATASOURCE_ID,
          }).then((res) => {
            if (res.success) {
              const fieldArr = res.data.split(',');
              formatExecField(fieldArr);
            }
          });
        } else {
          if (props.execData.fields) {
            formatExecField(props.execData.fields);
          }
        }
      });
      return {
        ...toRefs(state),
        ...methods,
      };
    },
  });
</script>
<style scoped lang="less">
  .exec-modal {
    width: 100%;
    height: 100%;
    padding: 0 20px;
    .exec-title {
      height: 40px;
      background: #f7f9fc;
      line-height: 40px;
      font-size: 14px;
      padding: 0 16px;
      color: #3265f5;
      box-sizing: border-box;
      border-left: 1px solid #e6e6e6;
      border-right: 1px solid #e6e6e6;
    }
    .exec-title-top {
      border-top: 1px solid #e6e6e6;
    }
    .exec-title-bottom {
      border-bottom: 1px solid #e6e6e6;
    }
    .exec-result {
      display: flex;
      justify-content: space-between;
      .exec-result-btns {
        display: flex;
        .exec-btn {
          margin-left: 15px;
          cursor: pointer;
        }
      }
    }
    .exec-form {
      width: 100%;
      height: 68px;
      padding: 18px 0px;
      box-sizing: border-box;
      border-left: 1px solid #e6e6e6;
      border-right: 1px solid #e6e6e6;
      .je-exec-form {
        width: 100%;
        height: 100%;
        display: flex;
        justify-content: space-around;
        .exec-param {
          width: 60%;
        }
        .exec-size {
          width: 20%;
        }
      }
    }
  }
  .custom-modal {
    width: 100%;
    height: 100%;
    .check-json-box {
      width: 100%;
      height: calc(100% - 20px);
    }
  }
</style>
